package ch.sv7.tool.dbmanager.db.difference;

import java.util.ArrayList;
import java.util.List;

import junit.framework.TestCase;
import ch.sv7.tool.dbmanager.db.SchemaElement;
import ch.sv7.tool.dbmanager.db.difference.filter.KeepBlockerDifferenceFilter;

/**
 * TODO: Document me!
 *
 * @author svt
 *
 */
public class SchemaDifferencesTestCase extends TestCase {

	public void testPreFilter() throws Exception {
		SchemaDifferences diffs = new SchemaDifferences();
		diffs.addFilter(new KeepBlockerDifferenceFilter());
		diffs.addDifference(new MockSchemaElement("atable"), new MockDifference("a1", true));
		diffs.addDifference(new MockSchemaElement("atable"), new MockDifference("a2", false));
		diffs.addDifference(new MockSchemaElement("column"), new MockDifference("a3", true));

		assertEquals(2, diffs.getSize());
		assertEquals("a1", diffs.getDifference(0).getMessage());
		assertEquals("a3", diffs.getDifference(1).getMessage());
	}
	
	public void testPostFilter() throws Exception {
		SchemaDifferences diffs = new SchemaDifferences();
		diffs.addDifference(new MockSchemaElement("atable"), new MockDifference("a1", true));
		diffs.addDifference(new MockSchemaElement("atable"), new MockDifference("a2", false));
		diffs.addDifference(new MockSchemaElement("column"), new MockDifference("a3", true));
		
		assertEquals(3, diffs.getSize());
		diffs.addFilter(new KeepBlockerDifferenceFilter());
		assertEquals(2, diffs.getSize());
		assertEquals("a1", diffs.getDifference(0).getMessage());
		assertEquals("a3", diffs.getDifference(1).getMessage());
	}
	
	public void testPreFilterWithFirstOnly() throws Exception {
		SchemaDifferences diffs = new SchemaDifferences();
		diffs.addFilter(new KeepBlockerDifferenceFilter());
		diffs.addDifference(new MockSchemaElement("atable"), new MockDifference("a1", true));
		List list = new ArrayList();
		list.add(new MockDifference("f1", false));
		list.add(new MockDifference("f2", true));
		diffs.addFirstDifferenceOfList(new MockSchemaElement("atable"), list);
		diffs.addDifference(new MockSchemaElement("atable"), new MockDifference("a2", false));
		diffs.addDifference(new MockSchemaElement("column"), new MockDifference("a3", true));
		

		assertEquals(3, diffs.getSize());		
		assertEquals("a1", diffs.getDifference(0).getMessage());
		assertEquals("f2", diffs.getDifference(1).getMessage());
		assertEquals("a3", diffs.getDifference(2).getMessage());
	}
	
	public void testPostFilterWithFirstOnly() throws Exception {
		SchemaDifferences diffs = new SchemaDifferences();
		diffs.addDifference(new MockSchemaElement("atable"), new MockDifference("a1", true));
		List list = new ArrayList();
		list.add(new MockDifference("f1", false));
		list.add(new MockDifference("f2", true));
		diffs.addFirstDifferenceOfList(new MockSchemaElement("atable"), list);
		diffs.addDifference(new MockSchemaElement("atable"), new MockDifference("a2", false));
		diffs.addDifference(new MockSchemaElement("column"), new MockDifference("a3", true));
		
		assertEquals(4, diffs.getSize());
		diffs.addFilter(new KeepBlockerDifferenceFilter());
		assertEquals(3, diffs.getSize());
		
		assertEquals("a1", diffs.getDifference(0).getMessage());
		assertEquals("f2", diffs.getDifference(1).getMessage());
		assertEquals("a3", diffs.getDifference(2).getMessage());
	}
	
	public void testPostFilterWithFirstOnlyEmpty() throws Exception {
		SchemaDifferences diffs = new SchemaDifferences();
		diffs.addDifference(new MockSchemaElement("atable"), new MockDifference("a1", true));
		List list = new ArrayList();
		list.add(new MockDifference("f1", false));
		diffs.addFirstDifferenceOfList(new MockSchemaElement("atable"), list);
		diffs.addDifference(new MockSchemaElement("atable"), new MockDifference("a2", false));
		diffs.addDifference(new MockSchemaElement("column"), new MockDifference("a3", true));
		
		assertEquals(4, diffs.getSize());
		diffs.addFilter(new KeepBlockerDifferenceFilter());
		assertEquals(2, diffs.getSize());
		
		assertEquals("a1", diffs.getDifference(0).getMessage());
		assertEquals("a3", diffs.getDifference(1).getMessage());
	}
	
	public class MockDifference implements SchemaDifference {
		private String message;
		private boolean blocker;

		public MockDifference(String message, boolean blocker) {
			super();
			this.message = message;
			this.blocker = blocker;
		}

		public String getMessage() {
			return message;
		}

		public boolean isBlocker() {
			return blocker;
		}	
	}
	
	public class MockSchemaElement implements SchemaElement {

		private String identifier;
		
		public MockSchemaElement(String identifier) {
			super();
			this.identifier = identifier;
		}

		public String getSchemaIdentifier() {
			return identifier;
		}
		
	}
}
